﻿//*** Guidance generated code ***//
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Mvc;

using ProjectBase.Core;
using ProjectBase.Core.Service;
using ProjectBase.Core.Web;
using ProjectBase.Mvc;
using ProjectBase.Mvc.Controllers;
using ProjectBase.Mvc.Views;

using $prjsn$.Common;
using $prjsn$.Common.Models.Services.HowTos;
using $prjsn$.Common.Controllers.Services.HowTos;
using $prjsn$.Common.Business.Services.HowTos;
using $prjsn$.Entity.Services.HowTos;

namespace $safeprojectname$.Controllers.Services.HowTos
{
    /// <summary>
    /// All actions for ComplexEntity
    /// </summary>
    [CLSCompliant(false)]
    public class ComplexEntityController : EntityController<ComplexEntity, long, ComplexEntityFilter, IComplexEntityModel, IComplexEntityFacade>, IComplexEntityController
    {
        #region OnList ToDisplay
        /// <summary>
        /// Provides columns for List view
        /// </summary>
        protected override IEnumerable<IItemToDisplay> LoadItemsToDisplay(ComplexEntityFilter filter)
        {
            return Facade.Find(filter)
                .Select(i => new ItemToDisplay
                {
                    ID = i.IDToDisplay,
                    Description = i.ToDisplay(),
                    Items = GetColumns(i, Model.Filter.ShowMoreCols),
                } as IItemToDisplay);
        }
        protected virtual IImageCellDescription GetImageCellDescription(ComplexEntity item)
        {
            var cell = new ImageCellDescription
            {
                HeaderName = "Image",
                Sort = false,
            };

            if (item.Image.IsNull())
            {
                return cell;
            }
            cell.Title = item.ToDisplay();
            cell.ImageUrl = Url.Action("Image", Str.Controllers.ComplexEntity, new { id = item.ID });

            return cell;
        }
        protected virtual IList<ICellDescription> GetColumns(ComplexEntity item, bool showMoreCols)
        {
            var list = new List<ICellDescription>
            {
                item.Cell(e => e.Code),
                GetImageCellDescription(item),
                item.Cell(e => e.ID, new CellDescription {Align = Align.right, Format = "N0"}),
            };

            return Model.Filter.ShowMoreCols
                ? GetMoreColumns(list, item)
                : GetFewColumns(list, item);
        }

        protected virtual IList<ICellDescription> GetFewColumns(List<ICellDescription> list, ComplexEntity item)
        {
            // this will append only two columns

            list.AddRange(new List<ICellDescription>
            {
                item.Cell(e => e.ShortName),
                item.Cell(e => e.VeryLongName),
                item.Cell(e => e.SimpleCombo),
                item.Cell(e => e.SimpleAsync),
                item.Cell(e => e.SimpleAuto),
            });
            return list;
        }
        protected virtual IList<ICellDescription> GetMoreColumns(List<ICellDescription> list, ComplexEntity item)
        {
            // some properties are commented to reduce the table size,
            // while still demonstrating the power

            list.AddRange(new List<ICellDescription>
            {
                item.Cell(e => e.IsApproved),
                //item.Cell(e => e.IsSigned),

                item.Cell(e => e.ByteValue),
                item.Cell(e => e.SByteValue),
                //item.Cell(e => e.ByteValueNullable),
                //item.Cell(e => e.SByteValueNullable),

                item.Cell(e => e.ShortValue),
                item.Cell(e => e.UShortValue),
                //item.Cell(e => e.ShortValueNullable),
                //item.Cell(e => e.UShortValueNullable),

                item.Cell(e => e.IntValue),
                item.Cell(e => e.UIntValue),
                //item.Cell(e => e.IntValueNullable),
                //item.Cell(e => e.UIntValueNullable),

                item.Cell(e => e.LongValue),
                item.Cell(e => e.ULongValue),
                //item.Cell(e => e.LongValueNullable),
                //item.Cell(e => e.ULongValueNullable),

                item.Cell(e => e.DecimalValue),
                //item.Cell(e => e.DecimalValue),
                item.Cell(e => e.FloatValue),
                //item.Cell(e => e.FloatValue),
                item.Cell(e => e.DoubleValue),
                //item.Cell(e => e.DoubleValue),

                item.Cell(e => e.ValidFrom),
                //item.Cell(e => e.ValidTo),
            });
            return list;
        }

        #endregion OnList ToDisplay

        #region OnList ToExcel
        /// <summary>
        /// Provides columns for Excel
        /// </summary>
        protected override IEnumerable<IEnumerable<IExCell>> LoadExcelItemsToDisplay(ComplexEntityFilter filter)
        {
            return Facade.Find(filter)
                .Select(i => new List<IExCell>
                {
                    i.ExCell(e => e.ID),
                    i.ExCell(e => e.Code),
                    i.ExCell(e => e.ShortName),
                    i.ExCell(e => e.VeryLongName),
                    i.ExCell(e => e.ByteValue),
                    i.ExCell(e => e.ByteValueNullable),
                    i.ExCell(e => e.SByteValue),
                    i.ExCell(e => e.SByteValueNullable),
                    i.ExCell(e => e.DecimalValue),
                    i.ExCell(e => e.DecimalValueNullable),
                    i.ExCell(e => e.DoubleValue),
                    i.ExCell(e => e.DoubleValueNullable),
                    i.ExCell(e => e.FloatValue),
                    i.ExCell(e => e.FloatValueNullable),
                    i.ExCell(e => e.GuidValue),
                    i.ExCell(e => e.GuidValueNullable),
                    i.ExCell(e => e.IntValue),
                    i.ExCell(e => e.IntValueNullable),
                    i.ExCell(e => e.UIntValue),
                    i.ExCell(e => e.UIntValueNullable),
                    i.ExCell(e => e.LongValue),
                    i.ExCell(e => e.LongValueNullable),
                    i.ExCell(e => e.ULongValue),
                    i.ExCell(e => e.ULongValueNullable),
                    i.ExCell(e => e.ShortValue),
                    i.ExCell(e => e.ShortValueNullable),
                    i.ExCell(e => e.UShortValue),
                    i.ExCell(e => e.UShortValueNullable),
                    i.ExCell(e => e.IsApproved),
                    i.ExCell(e => e.IsSigned),
                    i.ExCell(e => e.SimpleAsync),
                    i.ExCell(e => e.SimpleAuto),
                    i.ExCell(e => e.SimpleCombo),
                    i.ExCell(e => e.ValidFrom),
                    i.ExCell(e => e.ValidTo),
                });
        }
        #endregion OnList ToExcel

        #region On Async list
        protected override IEnumerable<IItemToDisplay> LoadAsyncItemsToDisplay(ComplexEntityFilter filter)
        {
            return Facade.Find(filter)
                .Select(i => new ItemToDisplay
                {
                    ID = i.IDToDisplay,
                    Description = i.ToDisplay(),
                    Items = GetFewColumns(new List<ICellDescription>
                    {
                        i.Cell(e => e.ID),
                        i.Cell(e => e.Code),
                    }, i),
                } as IItemToDisplay);
        }
        #endregion On Async list

        #region OnBind
        #endregion OnBind

        #region OnBefore
        protected override void OnBeforeList()
        {
            base.OnBeforeList();
            Model.MasterModel.ButtonSubmit = new ButtonItem(Str.Actions.NoView.Search)
            {
                FormController = ControllerName,
            };
        }
        #endregion OnBefore

        #region Actions
        #endregion Actions

        #region Image
        public virtual ActionResult Image(long? id)
        {
            if (id.IsNull())
            {
                return EmptyView();
            }
            if (Model.Item.IsNull()
                || !Model.Item.ID.Equals(id.Value))
            {
                Model.Item = Facade.GetById(id.Value);
            }

            if (Model.Item.Is()
                && Model.Item.Image.Is())
            {
                // simplified version expecting png only
                // to set file types ContentType could be used
                var model = Factory.CreateInstance<IExportModel>();
                model.DataOutput = Model.Item.Image;
                model.FileName = "Image";
                model.ContentType = "image/png";
                model.FileExtension = ".png";
                return new FileCoreResult(model);
            }
            return EmptyView();
        }
        #endregion Image

        #region ClearFilter
        /// <summary>
        ///     Pre-sets filtering filters
        /// </summary>
        protected override ComplexEntityFilter ClearFilter()
        {
            var filter = base.ClearFilter();
            // TODO set the MVC defaults e.g.: filter.OrderBy["ID"] = false;
            return filter;
        }

        #endregion ClearFilter

        #region properties
        public override string ControllerName { get { return Str.Controllers.ComplexEntity; } }

        // TODO:
        // e.g. IUserFacade if User instance is needed:
        // NOTE
        // if 'Project.config' file factoryProviderType is set:
        // value="ProjectBase.Data.Factory.IocWithProxyFactory, ProjectBase.Data
        // implementor of the 'IFacade' will be injected for you: LAZILY!

        // public virtual IUserFacade UserFacade { protected get; set; }

        #endregion properties
    }
}
